﻿/*************************************************************************************
 * 文 件 名:   IHK_SimpleTaskSystem
 * 
 * 描    述:   简单版-线性任务流管理系统，基于队列Queue
 * 
 * 版    本：  V1.1
 * 创 建 者：  京产肠饭
 * 创建时间：  2024/2/14
 * 链   接：  https://gitee.com/JingChanChangFan/hk_-unity-tools
*************************************************************************************/

using System.Collections.Generic;
using QFramework;
using UnityEngine;

namespace HKTools.SimpleTask
{
    public interface IHK_SimpleTaskSystem : ISystem
    {
        /// <summary>
        /// 初始化 一个 任务流
        /// </summary>
        void InitTaskQueue(TaskQueueType taskQueueType, List<TaskType> taskItems);

        /// <summary>
        /// 完成 指定任务流的 当前任务
        /// </summary>
        void CompleteCurrentTask(TaskQueueType taskQueueType);

        /// <summary>
        /// 完成 指定任务流的 指定任务
        /// </summary>
        void CompleteAppointTask(TaskQueueType taskQueueType, TaskType taskType);

        /// <summary>
        /// 中断 任务流
        /// </summary>
        void BreakUpTaskQueue(TaskQueueType taskQueueType);
    }

    public class HK_SimpleTaskSystem : AbstractSystem, IHK_SimpleTaskSystem
    {
        Dictionary<TaskQueueType, HK_TaskQueue> taskQueueDic;

        protected override void OnInit()
        {
            taskQueueDic = new Dictionary<TaskQueueType, HK_TaskQueue>();

            // 注册 任务流开始 事件
            this.RegisterEvent<Event_TaskQueueBegin>(args =>
            {
                Debug.LogFormat("<color=blue>-------开始任务流：{0}--------</color>", args._taskQueueType);
            });

            // 注册 任务流结束 事件
            this.RegisterEvent<Event_TaskQueueEnd>(args =>
            {
                Debug.LogFormat("<color=blue>-------结束任务流：{0}--------</color>", args._taskQueueType);
            });

            // 注册 任务流中断 事件
            this.RegisterEvent<Event_TaskQueueBreakUp>(args =>
            {
                Debug.LogFormat("<color=yellow>-------中断任务流：{0}--------</color>", args._taskQueueType);
            });

            // 注册 任务开始 事件
            this.RegisterEvent<Event_TaskStart>(args =>
            {
                Debug.LogFormat("<color=green>TaskStart: {0}</color>", args._taskType);
            });

            // 注册 任务完成 事件
            this.RegisterEvent<Event_TaskFinish>(args =>
            {
                Debug.LogFormat("<color=green>TaskFinish: {0}</color>", args._taskType);
            });
        }

        /// <summary>
        /// 初始化一个 任务流
        /// </summary>
        public void InitTaskQueue(TaskQueueType taskQueueType, List<TaskType> taskItems)
        {
            if (taskQueueDic.ContainsKey(taskQueueType))
            {
                Debug.LogWarning("该任务流程已经初始化过！");
                return;
            }

            HK_TaskQueue taskQueue = new HK_TaskQueue(taskQueueType, taskItems);
            taskQueueDic.Add(taskQueueType, taskQueue);

            taskQueueDic[taskQueueType].Begin();

            // 发送 任务流开始事件
            this.SendEvent(new Event_TaskQueueBegin()
            {
                _taskQueueType = taskQueueType
            }); ;

            // 发送 任务开始事件
            this.SendEvent(new Event_TaskStart()
            {
                _taskType = taskQueueDic[taskQueueType].currentTask
            });
        }

        /// <summary>
        /// 完成 指定任务流的 当前任务
        /// </summary>
        public void CompleteCurrentTask(TaskQueueType taskQueueType)
        {
            if (!taskQueueDic.ContainsKey(taskQueueType))
            {
                Debug.LogWarning("不存在该任务流!");
                return;
            }

            // 发送 任务完成 事件 
            this.SendEvent(new Event_TaskFinish()
            {
                _taskType = taskQueueDic[taskQueueType].currentTask
            });

            bool isOver = taskQueueDic[taskQueueType].PushTask();

            if (isOver)
            {
                taskQueueDic.Remove(taskQueueType);

                // 发送 任务流结束 事件
                this.SendEvent(new Event_TaskQueueEnd()
                {
                    _taskQueueType = taskQueueType
                }); ;
            }
            else
            {
                // 发送 任务开始 事件
                this.SendEvent(new Event_TaskStart()
                {
                    _taskType = taskQueueDic[taskQueueType].currentTask
                });
            }
        }

        /// <summary>
        /// 完成指定任务
        /// </summary>
        public void CompleteAppointTask(TaskQueueType taskQueueType, TaskType taskType)
        {
            if (!taskQueueDic.ContainsKey(taskQueueType))
            {
                Debug.LogWarning("不存在该任务流!");
                return;
            }

            if (taskQueueDic[taskQueueType].currentTask != taskType)
            {
                Debug.LogWarning(taskType + "不是当前任务，无法完成！");
                return;
            }

            // 发送 任务完成 事件 
            this.SendEvent(new Event_TaskFinish()
            {
                _taskType = taskQueueDic[taskQueueType].currentTask
            });

            bool isOver = taskQueueDic[taskQueueType].PushTask();

            if (isOver)
            {
                taskQueueDic.Remove(taskQueueType);

                // 发送 任务流结束 事件
                this.SendEvent(new Event_TaskQueueEnd()
                {
                    _taskQueueType = taskQueueType
                }); ;
            }
            else
            {
                // 发送 任务开始 事件
                this.SendEvent(new Event_TaskStart()
                {
                    _taskType = taskQueueDic[taskQueueType].currentTask
                });
            }
        }

        /// <summary>
        /// 中断 任务流
        /// </summary>
        public void BreakUpTaskQueue(TaskQueueType taskQueueType)
        {
            if (!taskQueueDic.ContainsKey(taskQueueType))
            {
                Debug.LogWarning("不存在该任务流!");
            }

            taskQueueDic[taskQueueType].Clear();
            taskQueueDic.Remove(taskQueueType);

            this.SendEvent(new Event_TaskQueueBreakUp { _taskQueueType = taskQueueType });
        }
    }

    /// <summary>
    /// 任务队列模板
    /// </summary>
    public class HK_TaskQueue
    {
        public TaskQueueType taskQueueType;

        public bool isBegin = false;
        public bool isEnd = false;

        // 任务队列
        public Queue<TaskType> taskQueue;

        public TaskType currentTask;

        int taskNum = 0;
        int taskCount = 0;

        // 当前任务进度
        public float TaskProcess
        {
            get { return taskNum * 1.0f / taskCount; }
        }

        public HK_TaskQueue(TaskQueueType taskQueueType, List<TaskType> taskItems)
        {
            this.taskQueueType = taskQueueType;
            this.taskQueue = new Queue<TaskType>();

            for (int i = 0; i < taskItems.Count; i++)
            {
                this.taskQueue.Enqueue(taskItems[i]);
            }

            taskCount = this.taskQueue.Count;

            taskNum = -1;
        }

        public void Begin()
        {
            isBegin = true;

            PushTask();
        }

        public bool PushTask()
        {
            if (!isBegin)
                return false;

            if (taskQueue.Count > 0)
            {
                TaskType task = taskQueue.Dequeue();
                currentTask = task;

                taskNum++;

                isEnd = false;
            }
            else
            {
                taskNum++;
                isEnd = true;
            }

            return isEnd;
        }

        public void Clear()
        {
            taskQueue.Clear();
        }
    }
}